(Aviso a navegantes: artículo práctico destinado principalmente a linuxeros con cámara de fotos digital. Quedan advertidos.)
Ésa de ahí arriba es una de las fotografías que saqué en mi reciente viaje a Londres. Así de lejos parece muy mona pero, si nos acercamos un poco, se ve algo muy feo:

¡Darwin está mirando fijamente a un píxel azul! Los píxeles calientes (aparecen normalmente rojos o azules) y los píxeles muertos (aparecen negros) están causados por fallos en el funcionamiento del CCD de la cámara. Suelen aparecer más cuanto más larga es la exposición de la imagen.
A los pocos días de comprar esta cámara que tengo ahora, en verano, encontré uno muy cantoso en una esquina, de color rojo. El servicio técnico me reparó la cámara, aunque se tiró su buen mes para hacerlo. Mientras buscaba por Internet qué era exactamente lo que hacían (me extrañaba la idea de que sustituyesen el CCD entero), leí que las cámaras internamente llevan un registro de qué píxeles están jodidos y su ubicación exacta, con lo que los ignoran a la hora de hacer la fotografía y utilizan para rellenar el hueco un valor sacado de la interpolación de los píxeles adyacentes. Al volver de Londres encontré otros dos puntos azules, pero me daba mucha pereza volver a enviar la cámara, sobre todo ahora que me vuelvo a ir a otra ciudad de vacaciones en breve; así que empecé a ver si me podía sacar las castañas del fuego yo solito.
Estuve buscando programas que corrigiesen ese defecto de forma sencilla, sin tener que editar cada imagen por separado y sin que tardasen demasiado en procesarlas todas. Mi primera opción fue buscar algún plugin para el GIMP, pero no tuve mucho éxito. Lo mejor que encontré fue este pequeño script que permitía procesar un directorio lleno de imágenes, pero tenía dos problemas:
- Había que introducir las coordenadas de cada píxel a mano. Si hay dos píxeles mal en cada imagen, hay que ejecutar el programa dos veces.
- El manoseo que realiza de las imágenes hace que la imagen corregida ocupe más que la imagen original. La lógica me dictaba que un píxel que ahora se parece más a los de su entorno debería ayudar a comprimir la imagen, no al revés.
Lo guardé por si acaso no encontraba nada mejor, pero buscando un poco más terminé llegando a una pequeña maravilla: jpegpixi.
‘Jpegpixi’ is short for ‘JPEG Pixel Interpolator’. The intent of the program is to interpolate pixels (single pixels, dots, stripes) in JPEG images. This is useful to correct images from a digital camera with CCD defects. For example, if one pixel is always bright green, this pixel can be interpolated with jpegpixi.
Es justamente lo que andaba buscando. Además viene junto con otro programa, jpeghotp, que detecta qué píxeles son más brillantes en una fotografía completamente negra y localiza automáticamente sus coordenadas (jpegpixi necesita saber dónde están los píxeles que tiene que corregir). El procedimiento normal para obtener una imagen sobre la que realizar este tipo de detección es el de sacar una fotografía con largo tiempo de exposición, y a oscuras, pero no fui capaz de conseguirlo con éxito: veía sólo uno de los puntos; de forma que tuve que encontrarlos a mano sobre alguna imagen antigua que ya los mostrase, usando display, por ejemplo. Simplemente hay que anotar la coordenada de la esquina superior izquierda (porque siempre aparecen como cúmulos de píxeles, aunque haya estado hablando todo el rato de un píxel único) y las dimensiones del cuadrado que se formaría. Ejemplo de lo que se ve en realidad:
Después de un rato de mirar y hacer pruebas, al final lo que tengo es un archivo de texto con este contenido:
579,527,7
1537,592,7
O dicho de otra forma: tengo dos puntos malos en mis fotografías. Uno está en 579×527 y el otro en 1537×592, y ambos grupos de píxeles defectuosos tienen unas dimensiones de 7×7. Si tenemos en cuenta que esto ocurre al disparar con un tamaño de imagen de 3264×2448 entendemos que es insignificante. El tamaño del cluster defectuoso lo he obtenido mediante ensayo y error, ejecutando el programa para una imagen y quedándome con el tamaño más pequeño que corrige el problema.
A continuación, y para terminar, hice un pequeño script que simplemente lanza este programa con todas sus opciones sobre toda imagen con extensión .jpg que haya en un determinado directorio:
#!/bin/sh
for imagen in *.jpg; do
echo -n “Corrigiendo $imagen… ”
jpegpixi -m 3 -f /home/chema/correccion_pixeles.txt $imagen $imagen.new
mv $imagen.new $imagen
echo “OK”
done
La opción -m 3 indica que quiero que se emplee interpolación bicúbica, y el resto simplemente indica el archivo de coordenadas, la imagen de origen y la imagen de destino (que luego machacará a la original). En mi ordenador de casa, un Centrino Duo a 2.2 GHz, tarda menos de un segundo en procesar un archivo del tamaño que he comentado antes. Y los resultados son impecables (y, efectivamente, ocupan menos que la imagen original):

Si esto le ha servido a alguien para arreglar sus fotos, bien está.




Sophie (#1) dice:
Que el gran Tux se acuerde de tí y te lluevan billetes de 500 lerus del techo de tu habitación xD
15/01/2009, 09:30Ponzonha (#2) dice:
Es una putada que ocurran este tipo de cosas, pero afortunadamente tenemos el software libre para arreglar los desaguisados. Me encanta que alguien haya pensado en escribir jpegpixi y jpeghot y me emociona que lo compartan.
15/01/2009, 09:43Breo (#3) dice:
Más que una putada, es una estafa. En unas cámaras que cuestan [500 €; ∞ €) estos fallos no deberían existir. Por otra parte, lo de un mes para arregler el fallo es de juzgado de guardia. [mode ironic on] Imagino que te dejarían una cámara de sustitución, ¿no? [mode ironic off]. Lo del sofware libre es el mejor invento después de los espejos en los ascensores.
15/01/2009, 10:16pnongrata (#4) dice:
Lo de que las imágenes pesan menos… ¿cuánto menos pesan? Porque se me ocurren dos explicaciones: o el script te recodifica la imagen con menos calidad (no creo), o bien te quita el EXIF, en cuyo caso la diferencia de tamaño oscilaría siempre alrededor de los 20 KB.
15/01/2009, 10:39Ryben (#5) dice:
Menudo rollo para arreglar un par de pixels mal colocados.
Basta con ir al Photoshop, utilizar la herramienta de “Clonar” y superponer encima del pixel defectuoso un fragmento adyacente de la imagen. 3 segundos. Listo.
15/01/2009, 11:15EC-JPR (#6) dice:
Aunque generalmente hables de otras cosas en el blog, se nota qué has estudiado, gorrión :D Y nos encanta.
#3: Por lo que tengo entendido, los servicios técnicos (y especialmente el de Canon) funcionan así. Según he oído a pofesionales, si mandas una réflex el plazo es algo menor, pero de las dos semanas no baja ni de coña.
15/01/2009, 11:20EC-JPR (#7) dice:
#5: Repite la jugada con diez fotos, y ya te sale rentable hacer todo ese “rollo”. Y si tienes para editar las de unas vacaciones, te merece la pena hasta instalar Linux para seguir los consejos del Rinze-tutorial™.
15/01/2009, 11:22Uno que pasaba (#8) dice:
Si no hace ningún tipo de “recompresión” que baje la calidad o las características de la foto, ese programa vale su peso en pixels…recuperados.
15/01/2009, 11:27Me guardo esta entrada, por si las moscas.
Nesta (#9) dice:
Yo tengo la misma cámara que tú. ¿Tienes instalado CHDK para poder disparar en RAW? A lo mejor alguien se ha currado un scrpipt para CHDK que haga eso cuando tomas la foto, y te ahorras incluso el procesamiento.
15/01/2009, 13:42Saludos.
la que no encuentra su sitio (#10) dice:
¡Qué grande! De momento no he tenido esos problemas, pero me lo apunto por-si-los-píxels ^_^
15/01/2009, 15:19meneame.net (#11) dice:
Muere, píxel inmundo…
Explicación de cómo corregir por software en Linux los errores de CCDs de cámaras digitales que generan píxeles calienes o píxeles muertos….
15/01/2009, 15:55Noid (#12) dice:
#5: Aha, Photoshop. Ese programa libre bajo la GPL… como dirían los guiris, “you’re missing the point”.
15/01/2009, 16:42David (#13) dice:
¡Oh gran Gauss! Si yo me acerco tanto a una foto y veo lo que debería estar enfocado así de borroso ¡ni veo el punto azul! (no es coña. Lo primero que he hecho al ver la ampliación ha sido gritar “¡borrosooo!”). Yo borraba la foto.
Que vale, que es tontería teniendo en cuenta de qué va el post porque si el pixel está jodido aunque la exposición sea más corta por ahí saldrá, aunque se note menos, pero chico, esa resolución, buf. No tiene mucho sentido preocuparse por un pixel cuando por lo borroso de la imagen a la foto le sobran tres cuartas partes, difuminados.
¿Apoyaste la cámara en alguna parte o la estabas sosteniendo a pulso? ¿Eso no sería con trípode, verdad? Si lo es, nada, enfoca o córtate el dedo, pero si no usabas trípode, para hacer fotos no borrosas apoya la cámara en algo inmóvil y dispara usando el temporizador, para que el propio dedo al hacer clic no la mueva.
En fin. Perdón por el integrismo antiborrosista. Es que me pueden estas cosas.
15/01/2009, 20:36Adrián (#14) dice:
Ese pequeño pixel es una forma en la que Dios te está demostrando que hasta la ciencia más exacta tiene imperfecciones y que no puedes vivir teniendo fe en esa realidad sostenida por alfileres.
15/01/2009, 21:01RinzeWind (#15) dice:
#3: bueno, la mía fue más barata, en torno a los 300 €, creo recordar.
#4: vienen a pesar unos 20k menos, depende de la imagen. En el caso de Darwin:
$ ls -l
total 6548
-rw-r–r– 1 chema chema 3317419 2009-01-15 22:04 darwin-corregido.jpg
-rw-r–r– 1 chema chema 3376751 2009-01-14 20:39 darwin.jpg
Los datos EXIF siguen en su sitio (lo acabo de comprobar). La prueba del algodón (que ahora no tengo tiempo para hacer, pero no es muy complicada) es restar ambas imágenes y ver si la única diferencia es en los puntos defectuosos. Si es así, no hay más diferencia que la corrección que se quiere realizar. Eso también va para #8. No parece que recomprima, a simple vista.
#5: como te dice EC-JPR, todo este pifostio me vale para cuando tenga que corregir 300 imágenes de una sentada.
#9: no conocía la existencia de ese invento, así que muchas gracias. Veré si me atrevo :-)
#13: fue sin trípode, a pulso. No es tanto que esté desenfocada sino que está movida. Fue medio segundo de exposición “a pelo”. Algo tenía que pasar.
#14: claro. ¡Mira detrás de ti, un mono de tres cabezas!
15/01/2009, 22:09Pedro Gimeno (#16) dice:
#15: Sobre la prueba del algodón que le comentas a #4, ten en cuenta que dada la naturaleza de la compresión JPEG, es prácticamente imposible que afecte únicamente a esos píxels. Lo más probable es que afecte a todos los cuadraditos (tiles) de 8×8 pixels donde cae ese rectángulo.
Y eso sólo si el programa lo hace bien y deja el resto de cuadraditos intactos. Supongo y espero que sí. La diferencia de tamaño me parece un poco alarmante, eso sí. No creo que un par de ruidos puntuales como esos sean causa para añadir 60K a la imagen, así que es posible que la recompresión de esos cuadraditos sea de peor calidad. Te recomiendo que mires a ver si el jpegpixi tiene ajuste de la calidad en la recompresión y que la subas en ese caso.
Ah, y recomiendo acostumbrarse a usar find en vez de for, por si los archivos exceden los 64K que suele tener como límite la línea de comandos. Y usar -f en el mv, por si el usuario tiene activa por defecto la opción -i del mv (como es mi caso).
#5 y #12, no es sólo un tema de libertad de software, que lo es; es que además (1) el resultado es de peor calidad y (2) no se puede aplicar en masa a todo un directorio de imágenes.
16/01/2009, 13:14coder (#17) dice:
Todo bien salvo porque ese echo OK debería ser un [[ $? -eq 0 ]] && echo OK || echo KO xD
16/01/2009, 14:09RinzeWind (#18) dice:
#15: he hecho la prueba. Efectivamente, afecta a algunos píxeles más, pero siempre alrededor de los defectuosos. No la he hecho con Darwin, sino con esta, que adolece de lo mismo. Tras restar la imagen original y la corregida y umbralizar el resultado, lo que se obtiene es esto.
Las diferencias están donde deberían estar, pero son más grandes de lo que yo pensaba. Esto puede ser porque la imagen original ya era ruidosa de por sí, por la compresión de la imagen o por motivos que ahora mismo no me vienen a la cabeza. En todo caso, las únicas diferencias son esas, así que no hay degradado en la imagen más allá de lo que el apaño necesita.
16/01/2009, 20:03Pedro Gimeno (#19) dice:
Sí, en el pixel de la izquierda tu región de 7×7 parece afectar a cuatro tiles o cuadraditos de 8×8 y en el de la derecha al parecer sólo a dos. Es cosa de la compresión jpeg, es inevitable. Se me escapa el motivo de que la diferencia izquierda abarque en realidad 18×16 en vez de 16×16 y la derecha 18×8 en vez de 16×8… tal vez sea al recomprimir la imagen de las diferencias, no sé.
La sugerencia de #9 sigue siendo la mejor idea, sin jpeg por medio.
16/01/2009, 22:25Adrián (#20) dice:
Dios mío, tanto escándalo por una fotografía que no avale un cacahuate. La gente sale movida, el encuadre es deplorable y el tema de lo más intrascendente. No cabe duda que el ocio es la madre de todos los vicios.
17/01/2009, 16:36Adrián (#21) dice:
Dios mío, tanto escándalo por una fotografía que no vale un cacahuate: La gente sale movida, el encuadre es deplorable y el tema de lo más intrascendente. No cabe duda que el ocio es la madre de todos los vicios, pero sobre todo de todos los desperdicios. Moraleja: si quieres una foto perfecta, cómprate una postal.
17/01/2009, 16:38DGLibre (#22) dice:
Una técnica interesante para casos concretos como el tuyo. Aunque he de reconocer que editar fotos mediante programación de scripts es muy retorcido para mi…
De todas formas me lo apunto, nunca se sabe.
18/01/2009, 01:05coder (#23) dice:
Adrián, y tú un flipao que no aporta nada positivo. Este post no va sobre la foto en sí, va sobre cómo arreglar un fallo de la cámara con software libre bajo Linux. Que estás tan agradecido de haberte conocido que ni te paras a ver de qué va el asunto.
18/01/2009, 14:54