jueves, 29 de diciembre de 2016

4.4 HTML: el juego de caracteres y los editores de texto

4.4  HTML: el juego de caracteres y los editores de texto

En un vídeo anterior ya te hablé del juego de caracteres y de los típicos problemas que ocasiona en las páginas web. En ese vídeo te daba dos consejos:
Utiliza siempre el mismo juego de caracteres en todo lo que hagas.
Y utiliza UTF-8 sin BOM, que te permite mezclar en un mismo documento textos en cualquier idioma.
Pero ya te avisé en el otro vídeo: hay que saber mucho, mucho más, ya que cuando las cosas empiezan a ir mal, esos dos consejos no son la solución para todos los problemas.
Hace unos días recibí el siguiente correo:
Estoy probando lo del juego de caracteres (usando Notepad++). En el vídeo recomiendas usar UTF8 sin BOM. Resulta que el fichero lo tengo con codificación ANSI, pero si lo cambio a UTF8 sin BOM, el disquete de guardar no se me marca (es decir, no se ha modificado el fichero). Entonces marco UTF8, se marca el disquete y guardo. Ahora selecciono UTF8 sin BOM. Se me marca el disquete y guardo (un pequeño chanchullo para que me permitiese guardar UTF8 sin BOM).
Y el correo continuaba:
Y ahora viene el tema. Si he guardado en UTF8 sin BOM, cuando cierro el fichero y lo vuelvo a abrir, la codificación que me marca es ANSI. ¿Es normal? También veo "Convertir a UTF sin BOM" además de "Codificar en UTF sin BOM" ¿cuál es la diferencia?

Bien, primero vamos a ver qué es eso del BOM. BOM es el acrónimo de Byte Order Mark, la Marca de Orden de Bytes y es un carácter Unicode que se utiliza para indicar el orden de los bytes de un fichero de texto al principio del fichero.
Básicamente existen dos órdenes de bytes, el little-endian y el big-endian, que definen de qué forma se almacenan los datos que ocupan más de un byte en el ordenador. ¿Confuso?
Sí, puede ser muy confuso. Ya sabes, para solucionar los problemas con los juegos de caracteres hay que saber mucho.
Volviendo al BOM, en el caso de UTF-8 es un carácter Unicode que ocupa 3 bytes y que tiene esta representación en hexadecimal y aparece representado de esta forma como carácter.
EF BB BF ï » ¿

¿Cuál es el problema de todo esto?
Lo mejor es utilizar UTF-8, nos evitamos problemas, podemos escribir cualquier carácter, podemos mezclar todos los idiomas del mundo.
Pero UTF-8 lleva el BOM, esos tres bytes al principio del fichero, y hay programas que no se llevan muy bien con el BOM.
Por ejemplo, PHP5 no tiene un soporte completo de UTF-8: si vamos a trabajar con PHP5, debemos de utilizar
UTF-8 sin BOM. Voy a realizar una demostración práctica con el editor Notepad++ para que lo entiendas mejor. Te voy a mostrar un problema típico que aparece cuando trabajamos con UTF8 y con PHP5.
Estoy en Notepad++ y he preparado tres ficheros de ejemplo para mostrarte el problema.
Por un lado tenemos este fichero html.html que contiene solamente código HTML.
Luego tenemos este fichero php.php que contiene esta instrucción de PHP, un echo, párrafo, “Esto lo escribe PHP”, que lo único que hace es escribir esta cadena de texto, esta cadena HTML.
Y por último también tenemos este fichero en PHP, php-file.php que lo único que hace es incluir la instrucción include de PHP para incluir el primer fichero de HTML, es decir, lo único que hace es leerlo y volcarlo en la salida.
Fíjate que los tres ficheros los tengo almacenados en formato UTF-8.
Vamos a ver cómo se visualizan estos tres ficheros en el navegador. Me voy al navegador y aquí tenemos el primer fichero, el de solamente HTML. Se ve bien, no hay ningún problema.
Luego tenemos el otro fichero, el que contiene código de PHP.  Se ve bien.
Y ahora el tercer fichero, este fichero de aquí, que contiene esta instrucción de PHP para cargar el primer fichero, es decir, se debería de ver igual que este fichero. Sin embargo, cuando lo visualizamos, notamos aquí que hay un cambio. Fijaros cómo aparece aquí un margen superior, como si hubiese aquí una línea adicional de texto.
¿Esto a qué es debido?
Si nos vamos ahora al código fuente, veremos que he añadido un comentario al principio de cada uno de los ficheros. ¿Este comentario debe producir ese espacio adicional?
No, para nada. Este espacio no lo debe producir un comentario. Es más, aquí lo podemos comprobar, como estos ficheros también tienen el comentario y sin embargo no aparece ahí ese espacio.
Por tanto, ¿a qué se debe esto? El problema está en que al cargar aquí en PHP este fichero, el fichero html.html, este fichero de aquí, recordad que está en formato UTF-8, lleva el BOM, aunque nosotros aquí no lo veamos.
¿Cómo lo puedo saber? Aquí en Notepad++ me he instalado un plugin que es un editor hexadecimal. Si le doy a ver el código hexadecimal del fichero, fijaros lo que tenemos aquí al principio. ¿Recordáis los tres caracteres que os he dicho “acordaros de estos tres caracteres”? Lo podemos ver aquí también en hexadecimal: ef bb bf.
Ese es el BOM, esa es la marca que indica que este es un fichero en formato UTF-8 e indica el orden de los bytes.
Este carácter es el que me está produciendo aquí este salto de línea, porque ese carácter está aquí incluido. Lo que ocurre es que el navegador tampoco me lo muestra aquí al ver el código fuente. Por tanto, me puedo volver loco, muy loco, buscando por qué me aparece aquí este margen. Y todo es debido a ese carácter invisible que no me aparece.
¿Cómo solucionamos este problema? Pues bien sencillo, la solución ya te la he dicho y es no almacenar el fichero en formato UTF-8, sino almacenarlo en formato UTF-8 sin BOM. Para eso nos vamos aquí al menú codificación, y le damos a “Convertir a UTF-8 sin BOM”. Pero aquí tenemos la duda, tenemos la pregunta que me hacían en un correo electrónico: ¿qué debo de usar, codificar o convertir?
Codificar lo debería de usar cuando inicio un fichero desde cero, es decir, cuando no tiene contenido. O cuando quiero hacer algo raro como almacenar en un mismo fichero caracteres con dos codificaciones distintas, porque lo que estoy indicando es que a partir de este momento, el contenido que yo escriba lo quiero codificar con este juego de caracteres, pero el contenido que ya tiene el fichero, lo dejamos en el juego de caracteres que ya tenía.
En nuestro caso no queremos hacer eso, no queremos dejar el fichero con la codificación anterior, sino que queremos transformar, convertir todos los caracteres a la nueva codificación. Por tanto debemos de usar convertir.
Yo te puedo asegurar que nunca he usado codificar. Esta opción nunca la he necesitado y la verdad es que si yo fuese el diseñador del Notepad++ la escondería un poco para no causar confusión entre los usuarios. Así que en este caso vamos a usar “Convertir a UTF-8 sin BOM”. Fijaros como me aparece en rojo para indicarme que el fichero ha sido modificado y lo que me ponían en el correo electrónico, ahora ya lo puedo guardar porque el fichero ha sufrido una transformación.
Al guardarlo me desaparece el disquete que se decía en el correo electrónico. El fichero no necesita guardarse porque no tiene ningún cambio y si me voy ahora al editor hexadecimal veréis que me han desaparecido esos tres caracteres que habían al principio. Ya no está el BOM, ya no está esa marca, ¿lo entendéis? Es bien sencillo.
Voy a realizar lo mismo con todos los ficheros, los voy a convertir a UTF-8 sin BOM. Ya los tengo los tres en UTF-8 sin BOM y vuelvo aquí, recargo, y veréis que aparentemente no ha habido ningún cambio. Efectivamente, porque el navegador Google Chrome está preparado para trabajar con UTF-8 con o sin BOM.
Pero ahora vamos a ver si se soluciona este problema, vamos a ver si desaparece este margen. Le doy a recargar y “ta chán”, ya no me sale ese margen. Genial, ¿no? Solucionado.
Esto es muy importante que lo recordéis, porque cuando trabajemos con PHP es muy normal hacer cosas como ésta, es decir, construir una página web mediante trozos, mediante componentes que los vamos incluyendo, los vamos uniendo.
Si nos despistamos y los componentes que vamos uniendo están almacenados en UTF-8 con BOM, nos aparecerá ese carácter no visible y nos romperá el diseño de la página web.
Por tanto, recordad: hay que almacenar los ficheros con UTF-8 sin BOM.
Y para finalizar, un último detalle. Acordaros que debéis poner la etiqueta <meta charset> para indicar el juego de caracteres. Y este juego de caracteres que indicamos aquí debe de coincidir con el juego de caracteres que físicamente se está empleando para almacenar el fichero. Si yo aquí indico un juego de caracteres y almaceno el fichero con otro juego de caracteres, tendré problemas.
Vamos a hacer una prueba. Por ejemplo, aquí tengo indicado UTF-8 como juego de caracteres para mi página y voy a cambiarlo a Latin1, por aquí está en algún sitio, pero bueno. Yo lo que hago es convertir a ANSI, fijaros como ahora me dice que tengo que guardar el fichero porque ha sufrido una transformación. Aquí me aparece efectivamente ANSI.  Le doy a guardar. Y ahora cuando cargue la página, “ta chán”,  ya no me aparece el carácter que me va a dar problemas. El carácter que me va a dar problemas es la vocal acentuada “á”. El resto de caracteres no me dan problema porque están entre los 128 primeros caracteres ASCII. Y esos caracteres se representan de igual forma en ASCII, en ISO-8859-1, en UTF-8. Como son los caracteres más comunes, siempre se representan igual, por eso no me dan problemas, los problemas me los dan los caracteres especiales.
Vamos a hacer otra prueba. Si yo ahora le pongo “latin1” o también le podría poner “iso-8859-1” pues, se debe de arreglar el problema. Volvemos al navegador, le doy a recargar y ya me sale bien el carácter otra vez.
Y ahora vamos a hacer la última prueba. Yo indico que mi juego de caracteres es en “latin”, lo tengo guardado en ANSI, bien es “latin1”. Le cambio la codificación y volvemos a UTF-8 sin BOM. Me vuelve a decir que lo guarde. Lo guardo. Recargar y “ta chán”, otra vez problema. Ahora me sale otro carácter distinto.
En conclusión, hay que llevar mucho cuidado y, lo que ponga aquí, lo que indiquemos en el HTML, tiene que coincidir con la codificación física del fichero. En cuanto haya una discrepancia, en cuanto no coincida, empezaremos a tener problemas.

Bien, espero que este vídeo te ayude un poco más a evitar los típicos problemas que aparecen al trabajar con los juegos de caracteres. Pero te vuelvo a recordar, el tema es muy complejo y hay que saber muchas cosas para hacer frente a todos los problemas que pueden surgir.



No hay comentarios:

Publicar un comentario