Usando GULP

Estoy usando GULP como gestor de tareas y es una maravilla. Es como tener un becario (que dios y los becarios me perdonen…) para encargarle tareas repetitivas.

Antes usaba SASS para compilar archivos .scss, pero los hace uno a uno, y cuando tenia que compilar un modulo que empleaban 30 o 40 archivos .css se hacia lento esperar a que acabara. GULP carga todos los archivos en memoria antes de trabajar con ellos y es mucho mas rápido. Además, me permite utilizar plugins como autoprefixer, que añade los prefijos para asegurar compatibilidad con los navegadores que le configures, incluso cronológicamente, yo lo tengo configurado para que me ponga los prefijos necesarios hasta 7 años de antigüedad. Así puedo escribir código mucho más rápido sin tenerme que preocupar de los moz- y los webkit-

Tambien lo uso para concatenar y minificar los .js, de esta forma acabo generando un único .css y un único .js para toda la pagina web y carga como un tiro.

Al ser la sintaxis de sass como la de .css puedo introducir en la compilacion css ajenos , como los de los reproductores de video, ahorrandome archivos y llamadas al servidor.

También sirve muy bien para realizar tareas repetitivas que no pueden ser conseguidas con un simple batch. Tuve un caso similar al siguiente en el trabajo, localizar una serie de archivos html que hacían referencia a una imagen map.png que no estaba en su carpeta /img, generando un error 404.

Podría haber localizado los .html con un buscador por contenido, pero luego habría tenido que mirar carpeta por carpeta si el map.png se hallaba ahí, hablamos de unos 400 archivos html de los cuales la mitad podían estar en esa situación.

Os pongo el codigo utilizado en el script GULP que utilicé para localizarlos, con una explicación paso a paso de lo que hace:

 var gulp = require('gulp');  //carga gulp
 var contains = require('gulp-contains');  //carga plugin para buscar textos
 var fs = require('fs');  //carga plugin para buscar archivos
 var counter = 0;  //variable contador de archivos
 gulp.task('busca', function() {  //abre proceso 'busca'     
 gulp.src('es/**/trivia.txt')    //carga archivos sobre los que trabajar, todos  los html de todas las subcarpetas en la carpeta /es
 .pipe(contains({   //añade plugin contains
     search: 'map.png', //busca esta cadena
     onFound: function(string, file, cb) { //cuando la encuentre....
     try {
         fs.accessSync(file.path.slice(0, -10) + "img/map.png"); //...a partir del path del archivo, busca el archivo map.png
     } catch (e) { //si no lo encuentra...  
         counter ++;//actualiza el contador...
         console.log(counter +":"+ file.path.slice(0, -9)); //...y muestra la ruta  en la consola ("restando" map.png)
         return false }  //cierro  fs.accessSync                 
     return false;} //cierro search           
     }))    //cierro  contains
    .pipe(gulp.dest(function(file) {return file.base;})) });  //path de destino de los archivos *
gulp.task('default', ['check']);  //arranca al hacer gulp en el terminal

* en este caso, no seria necesario porque no realizo ningún proceso con los archivos, pero GULP lo necesita para funcionar correctamente, sino, detiene la búsqueda en los 16 primeros.

Menú desplegable sin JS

Cada vez más aprecio las webs ligeras, especialmente cuando me quedo sin datos en el móvil o estoy en un sitio con mala conexión. Hace poco no pude leer un articulo porque el “leer más” iba por javascript y no llegaba a arrancar a pesar de que el contenido ya estaba cargado, seguia cargando .js y cosas que bloqueaban el arranque de JS (que no ocurre, en principio, hasta haber cargado todos los contenidos de la pagina).

Puede ser muy frustrante que un visitante no pueda desplegar un menú para llegar a la sección que le interesa porque la pagina está bloqueada cargando cosas que no necesita (y no vamos a entrar en las estadísticas discutibles de Google sobre los 3 segundos que puede aguantar un navegante esperando una carga)
Para evitarlo, esta es una forma de crear interacción que funciona desde el momento en que se renderiza la pagina, sin tener que esperar la carga de jquerys y demas y quedarse bloqueada la funcionalidad.

Se basa en el los selectores  “~” que significa “aquellos elementos que comparten padre” (ojo, DESPUES del elemento referenciado) , y en “input:checked” .

El tema es colocar un <input> con opacity:0 para que no se vea, y colocado de forma absoluta dentro del elemento de menu con medidas al 100% para habilitar el pulsado de todo el botón. A partir de ahí, podemos aplicarle propiedades a sus “hermanos”  así:

input ~ div: (sin pulsar, plegado)
input:cheked ~ div : pulsado(desplegado).

Combinado con transition se hacen animaciones suaves para el desplegado.

Esto tiene un problema, y es que si hay varios items de menú desplegables, no podemos hacer mediante css que al pulsar  uno se plieguen los demás. He intentado hacerlo con elementos radio button, que solo permiten seleccionar uno de entre varios, pero hasta el momento no lo he conseguido.
Para resolverlo si que debemos usar una pequeño JS que deseleccione los demás items al pulsar uno de ellos, lo mas cómodo es usar .siblings() de Jquery en una función que deseleccione los demás inputs al seleccionar uno.

Si, acabamos usando JS, pero al menos ya se puede desplegar el menú sin esperas innecesarias desde el primer render de la pagina.

Aquí teneis un codepen sencillo explicando el concepto, en este caso se ha cambiado la opacidad del menu, pero se podria haber cambiado cualquier otra propiedad del <ul> o de los <li>s