Convertir una imagen JPG a Webp con javascript

Convertir una imagen JPG a Webp como frontend developers es una iniciativa que tomar en algún momento, en mejora de una rapida visualizacion de un sitio web en el que estemos trabajando. Mejorando así el SEO con los tiempos de respuestas desde el servidor.

Es fácil enfocarse en el rendimiento de una web para SEO desde la optimización y compresión de imágenes jpg o png. Pero aún así queremos resultados muchos mejores en el tiempo de respuesta, para ello desde hace unos años una de las opciones que se maneja para las imágenes es WEBP, un formato creado en el 2010 por Google.

Existen algunos frameworks react que convierten todas las imágenes en formatos amigables para el SEO, son los casos de Gatsby JS y Next JS son quienes van a la cabeza de los JAMSTACK’s.

Para este ejemplo voy a usar un input tipo archivo con una id única y lo guardaremos en una variable para su posterior uso. Ya sea para mostrar en una web o para subirla a un servidor.

Como convertir una imagen JPG a Webp?

<input type="file" id="file" accept=".jpge,.jpg,.png"/>

Tenemos un input tipo file con un id igual tipo file. Además del atributo «accepts» que solo permitirá archivos de imágenes con la extensión: jpge, jpg y png. Esta es la primera validación y única haré para este ejemplo.

Lo que sigue es solo JavaScript y este puede estar dentro del archivo html en el que están trabajando un creando uno nuevo.

const fileImage = document.getElementById('file')
let webpImage = ""
let brandImage = document.querySelector(#image)
const reader = new FileReader()

fileImage.addEventListener("change", () => {
    const fileName = fileImage.files[0].name.slice(0, -4)
    reader.readAsDataURL(fileImage.files[0])
    reader.onload = e => {
    const image = new Image()
    image.src = e.target.result
    image.onload = () => {
       const canvas = document.createElement('canvas')                    
       canvas.width = image.naturalWidth
       canvas.height = image.naturalHeight
       canvas.getContext('2d').drawImage(image, 0, 0)
       canvas.toBlob((blob) => {
           webpImage = new File([blob], `${fileName}.webp`,
                       {type: blob.type})
           brandImage.src = URL.createObjectURL(webpImage)
           }
         }
        })
})

Todo este proceso tiene dos salidas:

  • WebpImage: Recibe la imagen ya transformada en el formato WebP y con el nombre del archivo original. Esta es la variable que vamos a usar en caso de que queramos subir dicho archivo al servidor.
  • brandImage: Este es en caso de que queramos mostrar en el navegador dentro del atributo src de la etiqueta imágen.

Ya que estamos aqui, podríamos hacer las validaciones de dimensiones del archivo en caso de que queramos un tamaño en específico.

Para ello, añadimos el siguiente código, por debajo de la función «image.onload«:

Con esta validación lo que estamos haciendo es no permitirle a los usuarios subir imágenes mayores de 400px ancho y 200px de alto y detendrá el proceso en caso de que no se cumplan las condiciones.

const {
   height,
   width
} = image;

if(height != 200 || width != 400){
   alert("Las medidas para subir una imagen debe ser de 400x200px");
   return false;
}

Para completar el ejercicio, completo el HTML para mostrar la imagen WebP y con un click subir la imagen.

<input type="file" id="file" accept=".jpge,.jpg,.png"/>
<img src="" id="image" class="" />
<button id="upload" type="submit">Subir imagen</button>

Agregando las validaciones obtendremos un código similar.

const fileImage = document.getElementById('file')
const brandImage = document.querySelector(#image)
const uploadImage = document.getElementById("upload")
let webpImage = ""
const reader = new FileReader()

fileImage.addEventListener("change", () => {
    const fileName = fileImage.files[0].name.slice(0, -4)
    reader.readAsDataURL(fileImage.files[0])
    reader.onload = e => {
    const image = new Image()
    image.src = e.target.result
    image.onload = () => {
       const {
         height,
         width
       } = image;

       if(height != 200 || width != 400){
         alert("Las medidas para subir una imagen debe ser de
         400x200px");
         return false;
       }

       const canvas = document.createElement('canvas')                    
       canvas.width = image.naturalWidth
       canvas.height = image.naturalHeight
       canvas.getContext('2d').drawImage(image, 0, 0)
       canvas.toBlob((blob) => {
           webpImage = new File([blob], `${fileName}.webp`,
                       {type: blob.type})
           brandImage.src = URL.createObjectURL(webpImage)
           }
         }
        })
})

uploadImage.addEventListener("click", () => {
   //Código fetch para subir lo que hay en webpImage cuando se haga click en el botón
}

Con este sencillo script le damos todas las validaciones y la transformación al navegador y no enviamos nada al servidor hasta que la imagen está transformada. Convertir una imagen JPG a WebP con javascript en el navegador nos permite justamente eso.

Es quizás una tontería pensar transformar las imágenes desde un inicio del proyecto, pero una vez que el proyecto esté crecido, implementar estos cambios se nos hará complicado convertir todas las imagenes que ya tenemos en el servidor.

Deja un comentario

Tu dirección de correo electrónico no será publicada. Los campos obligatorios están marcados con *