Brillo y Contraste#
Al visualizar imágenes en cuadernos Jupyter, es importante mostrarlas de manera que el lector pueda ver de lo que estamos escribiendo. Por lo tanto, ajustar el brillo y el contraste es importante. Podemos hacer esto modificando el rango de visualización, el rango de valores de gris mostrados.
Para fines de demostración, utilizamos la imagen de ejemplo cells3d de scikit-image.
import numpy as np
import matplotlib.pyplot as plt
from skimage.data import cells3d
El conjunto de datos cells3d es una imagen 4D. Usando acceso a arrays, extraemos un solo corte 2D y lo mostramos.
image = cells3d()[30,0]
image.shape
(256, 256)
plt.imshow(image, cmap='gray')
plt.colorbar()
<matplotlib.colorbar.Colorbar at 0x1b3bba94a90>
Observe que aquí la barra de colores va desde 0 hasta aproximadamente 45000. La función plt.imshow() de matplotlib ajusta el contraste de la imagen a los valores mínimos y máximos.
Los valores mínimos y máximos de píxeles también se pueden obtener de esta manera:
min_value = image.min()
max_value = image.max()
print('min value = ', min_value)
print('max value = ', max_value)
min value = 277
max value = 44092
Si queremos aumentar el brillo, es decir, la percepción de que la imagen está emitiendo más luz, podemos configurar el rango de visualización estableciendo su mínimo vmin y máximo vmax. Esto mejora la visibilidad de las membranas.
plt.imshow(image, cmap='gray', vmax=10000)
plt.colorbar()
<matplotlib.colorbar.Colorbar at 0x1b3bbb1dbb0>
Ajustando la visualización independientemente de la imagen específica#
La próxima imagen que abramos puede tener, o no, un rango de valores de gris similar. Por lo tanto, podríamos inspeccionar el histograma de la imagen y adivinar un mejor umbral manualmente.
plt.hist(image.ravel())
(array([5.8622e+04, 5.6930e+03, 9.7800e+02, 1.6900e+02, 5.5000e+01,
1.0000e+01, 5.0000e+00, 1.0000e+00, 2.0000e+00, 1.0000e+00]),
array([ 277. , 4658.5, 9040. , 13421.5, 17803. , 22184.5, 26566. ,
30947.5, 35329. , 39710.5, 44092. ]),
<BarContainer object of 10 artists>)
Los histogramas de imágenes a menudo se muestran con una escala logarítmica.
plt.hist(image.ravel(), log=True)
(array([5.8622e+04, 5.6930e+03, 9.7800e+02, 1.6900e+02, 5.5000e+01,
1.0000e+01, 5.0000e+00, 1.0000e+00, 2.0000e+00, 1.0000e+00]),
array([ 277. , 4658.5, 9040. , 13421.5, 17803. , 22184.5, 26566. ,
30947.5, 35329. , 39710.5, 44092. ]),
<BarContainer object of 10 artists>)
Obviamente, esta imagen tiene muchos valores de gris oscuros (< 20000) y pocos valores > 40000.
Podría tener sentido configurar la visualización utilizando un porcentaje. Supongamos que queremos visualizar la imagen de manera que el 95% de los píxeles estén dentro del rango. Podemos hacer esto usando el método percentil de numpy. También volveremos a los percentiles al final del semestre.
upper_limit = np.percentile(image, 95)
upper_limit
6580.0
plt.imshow(image, cmap='gray', vmax=upper_limit)
plt.colorbar()
<matplotlib.colorbar.Colorbar at 0x1b3bd17e670>
Ejercicio#
El conjunto de datos cells3d contiene otro canal que muestra los núcleos de las células. Visualízalo de manera que el 99% de los valores de gris más bajos se visualicen adecuadamente.
nuclei = cells3d()[30,1]
nuclei.shape
(256, 256)