Qu'est ce que le format "webp" et pourquoi générer des images webp à la volée ?

Le poids des pages étant un grand frein au bon référencement naturel, le format WebP (prononcé “weppy”) est un format d’image moderne développé par Google, conçu pour fournir une meilleure compression d’image tout en conservant une qualité visuelle élevée. Il est utilisé pour les images sur le web et permet d’obtenir des fichiers plus légers par rapport aux formats plus traditionnels tels que JPEG ou PNG. WebP prend en charge à la fois la compression avec perte et la compression sans perte, ainsi que la transparence (comme PNG), ce qui le rend polyvalent pour différents types d’images.

Les plugins de compression d'images WordPress

Vous en trouverez beaucoup, plus ou moins chers, plus ou moins complets, plus ou moins “usine à gaz” à paramétrer, plus ou moins…lourds. Vous trouverez aussi de nombreux sites qui les comparent, dont voici un exemple ici (en anglais).

Un petit plugin léger et efficace pour générer des images webp à la volée

Vous l’avez compris, le but de wp-codes.fr est de vous fournir des ressources entièrement gratuites, simples, légères et fonctionnelles. Je vous propose donc le code du petit plugin que j’utilise, avec de nombreux commentaires pour que vous compreniez à quoi sert chaque ligne de code.

Préalable : vérifier les bibliothèques d'image sur votre serveur

Ce plugin, comme la plupart des plugins de compression d’images, utilise les bibliothèques PHP GD ou IMAGICK (les 2 cas sont prévus). Il est donc primordial de savoir si elles sont activées sur votre serveur. Si vous avez accès à une section “Configuration PHP”, les infos se trouvent sûrement ici. Si ce n’est pas le cas, vous pouvez créer une page nommée infos.php et la placer à la racine de votre installation WordPress. Dans ce fichier, collez simplement le code suivant :

				
					<?php
phpinfo();
?>
				
			

Puis affichez cette page dans votre navigateur : https://votre-site.com/infos.php pour afficher la configuration PHP de votre serveur. Recherchez maintenant (avec CTRL+F) les termes GD et IMAGICK. Vous devez voir :

Images webp à la volée, vérifier GD

Comme vous le voyez, sur mon serveur Hostinger, les 2 bibliothèques sont chargées et actives. Poursuivons maintenant avec le fichier de notre plugin Images webp à la volée.

Le code détaillé du plugin pour des images webp à la volée

Dans votre dossier plugins (wp-content/plugins) créez un dossier convert-to-webp dans lequel vous ajouterez un fichier nommé convert-to-webp.php puis collez le code suivant dans le fichier :

				
					<?php
/**
 * Plugin Name: générer des images webp à la volée
 * Description: Convertit automatiquement les images téléchargées au format WebP à l'aide d'Imagick ou de GD, avec une page de réglages administratifs pour ajuster la qualité.
 * Version: 1.6
 * Author: WP-CODES
 * Author URI: https://wp-codes.fr
 */

// Empêche l'accès direct au fichier pour des raisons de sécurité
if (!defined('ABSPATH')) {
    exit;
}

class ConvertToWebP {

    // Définir une valeur par défaut pour la qualité de compression WebP
    private $default_quality = 80;

    // Constructeur : il s'exécute automatiquement à l'initialisation du plugin
    public function __construct() {
        // Attacher la conversion WebP au processus d'upload d'image via la médiathèque
        add_filter('wp_handle_upload', [$this, 'convert_image_to_webp']);
        // Ajouter le support des fichiers WebP dans la médiathèque de WordPress
        add_filter('mime_types', [$this, 'allow_webp_uploads']);
        // Ajouter une page de réglages dans le menu Médias
        add_action('admin_menu', [$this, 'add_settings_page']);
        // Enregistrer les options de réglage (qualité de compression)
        add_action('admin_init', [$this, 'register_settings']);
    }

    /**
     * Fonction de conversion en WebP.
     * Appelée chaque fois qu'une image est uploadée dans la médiathèque.
     */
    public function convert_image_to_webp($upload) {
        // Vérifier si le fichier uploadé est une image supportée (JPEG, PNG, GIF)
        $file_type = wp_check_filetype($upload['file']);
        $allowed_types = array('image/jpeg', 'image/png', 'image/gif');

        // Si le fichier est une image valide, continuer
        if (in_array($file_type['type'], $allowed_types)) {
            // Obtenir le chemin complet du fichier image
            $image_path = $upload['file'];

            // Récupérer la qualité de compression depuis les options enregistrées (ou la valeur par défaut)
            $quality = get_option('webp_conversion_quality', $this->default_quality);

            // Convertir l'image en WebP
            $webp_path = $this->convert_to_webp($image_path, $quality);

            // Si l'image WebP est créée avec succès, l'ajouter à la médiathèque
            if ($webp_path) {
                $this->add_webp_to_media_library($webp_path, $upload);
            }
        }

        return $upload; // Retourner l'upload d'origine pour qu'il continue normalement
    }

    /**
     * Convertir une image en WebP en utilisant soit Imagick, soit GD.
     */
    private function convert_to_webp($image_path, $quality) {
        // Obtenir les informations sur le chemin et nom de fichier
        $info = pathinfo($image_path);
        // Créer un chemin pour l'image WebP
        $webp_path = $info['dirname'] . '/' . $info['filename'] . '.webp';

        // Si un fichier WebP existe déjà avec le même nom, ne pas le recréer
        if (file_exists($webp_path)) {
            return $webp_path;
        }

        // Utiliser Imagick si l'extension est disponible sur le serveur
        if (extension_loaded('imagick')) {
            $imagick = new Imagick();
            $imagick->readImage($image_path);
            $imagick->setImageFormat('webp');
            // Définir la qualité de compression avec la valeur obtenue des réglages
            $imagick->setImageCompressionQuality($quality);
            $imagick->writeImage($webp_path);
            $imagick->clear();
            $imagick->destroy();
            return $webp_path; // Retourner le chemin du fichier WebP
        }

        // Si Imagick n'est pas disponible, utiliser la bibliothèque GD
        elseif (extension_loaded('gd')) {
            $image = null;
            // Détecter le type MIME pour savoir comment traiter l'image
            $mime_type = mime_content_type($image_path);
            switch ($mime_type) {
                case 'image/jpeg':
                case 'image/jpg':
                    $image = imagecreatefromjpeg($image_path);
                    break;
                case 'image/png':
                    $image = imagecreatefrompng($image_path);
                    break;
                case 'image/gif':
                    $image = imagecreatefromgif($image_path);
                    break;
                default:
                    return;
            }
            if ($image) {
                // Créer le fichier WebP avec GD et appliquer la qualité définie
                imagewebp($image, $webp_path, $quality);
                imagedestroy($image); // Libérer la mémoire après traitement
                return $webp_path; // Retourner le chemin du fichier WebP
            }
        }

        return null; // Retourner null si la conversion n'a pas pu être effectuée
    }

    /**
     * Ajouter le type MIME WebP à la liste des fichiers autorisés dans la médiathèque.
     */
    public function allow_webp_uploads($mimes) {
        // Ajouter .webp en tant que type de fichier image autorisé
        $mimes['webp'] = 'image/webp';
        return $mimes;
    }

    /**
     * Ajouter l'image WebP à la médiathèque comme une pièce jointe.
     */
    private function add_webp_to_media_library($webp_path, $original_upload) {
        // Obtenir le type MIME de l'image WebP
        $wp_filetype = wp_check_filetype($webp_path, null);
        // Préparer les informations d'attachement pour la médiathèque
        $attachment = array(
            'guid'           => $original_upload['url'], // URL d'origine pour cohérence
            'post_mime_type' => $wp_filetype['type'],    // Type MIME de WebP
            'post_title'     => sanitize_file_name(basename($webp_path)), // Titre de l'image
            'post_content'   => '',
            'post_status'    => 'inherit' // Statut pour attachement
        );

        // Insérer l'image WebP dans la médiathèque
        $attach_id = wp_insert_attachment($attachment, $webp_path);
        
        // Générer et ajouter les métadonnées pour l'image WebP
        require_once(ABSPATH . 'wp-admin/includes/image.php');
        $attach_data = wp_generate_attachment_metadata($attach_id, $webp_path);
        wp_update_attachment_metadata($attach_id, $attach_data);
    }

    /**
     * Ajouter une page de réglages sous le menu Médias.
     */
    public function add_settings_page() {
        add_media_page(
            'Réglages de conversion WebP',  // Titre de la page
            'Conversion WebP',              // Titre du menu
            'manage_options',               // Capacité requise pour voir cette page
            'webp_conversion_settings',     // Slug de la page de réglages
            [$this, 'render_settings_page'] // Fonction pour afficher le contenu de la page
        );
    }

    /**
     * Afficher la page de réglages dans l'interface admin.
     */
    public function render_settings_page() {
        ?>
        <div class="wrap">
            <h1>Réglages de conversion WebP</h1>
            <form method="post" action="options.php">
                <?php
                // Générer les champs cachés pour enregistrer les options
                settings_fields('webp_conversion_settings_group');
                // Afficher les sections de réglages définies
                do_settings_sections('webp_conversion_settings');
                // Afficher le bouton pour soumettre le formulaire
                submit_button();
                ?>
            </form>
        </div>
        <?php
    }

    /**
     * Enregistrer les réglages dans la base de données WordPress.
     */
    public function register_settings() {
        // Enregistrer l'option pour la qualité de compression
        register_setting(
            'webp_conversion_settings_group',  // Groupe de réglages
            'webp_conversion_quality',         // Nom de l'option
            [
                'type' => 'integer',
                'description' => 'Qualité de compression pour les fichiers WebP (0-100)',
                'default' => $this->default_quality,
                'sanitize_callback' => 'absint', // Assurer que c'est un entier positif
            ]
        );

        // Ajouter une section pour les réglages de la qualité
        add_settings_section(
            'webp_conversion_settings_section', // ID de la section
            'Qualité de conversion WebP',       // Titre de la section
            null,                               // Pas de description nécessaire
            'webp_conversion_settings'          // Slug de la page
        );

        // Ajouter le champ de saisie pour la qualité
        add_settings_field(
            'webp_conversion_quality',          // ID du champ
            'Qualité de compression (0-100)',   // Label du champ
            [$this, 'render_quality_field'],    // Fonction pour afficher le champ
            'webp_conversion_settings',         // Slug de la page de réglages
            'webp_conversion_settings_section'  // Section où placer ce champ
        );
    }

    /**
     * Afficher le champ de saisie pour la qualité de compression dans la page de réglages.
     */
    public function render_quality_field() {
        // Récupérer la valeur actuelle de la qualité
        $quality = get_option('webp_conversion_quality', $this->default_quality);
        // Afficher un champ de saisie de type number pour entrer la qualité
        echo '<input type="number" name="webp_conversion_quality" value="' . esc_attr($quality) . '" min="0" max="100" />';
    }
}

// Initialiser le plugin
new ConvertToWebP();

				
			

Ce que fait ce code

Chaque ligne de code est commentée afin que vous puissiez comprendre le mécanisme, mais, en gros :

  • Conversion d’images webp à la volée : Le plugin convertit les images JPEG, PNG et GIF uploadées en fichiers WebP plus optimisés.
  • Page de réglages : Une page de réglages dans le menu “Médias” permet de définir la qualité de compression des images WebP, allant de 0 (compression maximale) à 100 (qualité maximale).
  • Fonctionnalités dynamiques : La qualité de compression est ajustée dynamiquement via la base de données WordPress, sans avoir besoin de modifier le code source du plugin.
  • Utilisation de GD ou Imagick : Le plugin utilise la bibliothèque Imagick (si disponible) pour une meilleure gestion des images, sinon il bascule vers GD, qui est plus largement disponible sur les serveurs.

En conclusion

Installez le plugin via votre installateur d’extensions WordPress comme d’habitude et activez-le. Désormais, toutes les images au format JPG, PNG ou GIF seront automatiquement générées en images webp à la volée.

Dans le menu Médias, vous verrez un sous-menu “Compression Webp” qui est la page de réglage de la compression. Plus le chiffre est élevé, plus la compression sera importante et la qualité moindre. Personnellement j’ai mis 60, mais c’est à vous de faire des tests et trouver le meilleur compromis qui vous convient.

Bien entendu si votre site est un portfolio de vos plus belles photos de vacances, vous souhaiterez sans doute avoir la meilleure qualité possible (et tant pis pour le poids), mais si vos images sont simplement là pour illustrer un propos, alors vous voudrez les compresser d’avantage. Avec la qualité réglée à 60, je passe d’une image JPG de 1400 ko à une image webp de 240 ko…ce qui à mon sens est encore trop. Dans ce cas il sera sans doute utile de réduire les dimensions de votre image de base. Mon image test faisait 1800px x 1400 px. Vous pouvez voir cet article sur le redimensionnement d’images uploadées

Téléchargez le plugin images webp à la volée

Laisser un commentaire