Come generare miniature solo quando necessario?


18

Ho 1000 immagini. Come posso fare wordpress per generare pollice solo quando necessario. Ad esempio, il dispositivo di scorrimento Home utilizzerà solo 10 immagini che non voglio che le altre 1000 immagini abbiano quella miniatura generata come uno spreco di spazio e risorse.

C'è un modo per licenziare add_image_size solo quando necessario?

Grazie

AGGIORNAMENTO Come hai detto, in realtà non è add_image_size ciò che deve essere attivato. Sarebbe fantastico sparare il ridimensionamento dell'immagine quando uso the_post_thumbnail ('slider-thumb'); Forse questo rallentamento della prima vista dell'immagine, ma quella vista è di solito generata da me quando in realtà rivedo il post, quindi non mi interessa.

Quindi tra i miei post, il dispositivo di scorrimento, le miniature dei blog, le miniature del portfolio, ecc. Ho ottenuto 1000 immagini e voglio ridimensionare solo 10 immagini per il dispositivo di scorrimento, vedo molte risorse sprecate per generare le dimensioni delle miniature per le altre 990 immagini.

Spero sia chiaro ora, scusate il mio inglese


2
In che modo le miniature generate dalle 990 immagini extra sono più uno spreco di spazio e risorse rispetto alle 990 immagini inutilizzate? Non avrebbe più senso caricare solo le immagini che stai utilizzando attivamente?
SickHippie,

Anche se programmatori più qualificati presentano argomenti validi contro la tua idea, la trovo interessante. Ho visto alcuni plugin e temi che caricano immagini senza generare pollici (non sono sicuro di quale al momento). Ma il mio grande dubbio sulla tua domanda è: quando ne avrai bisogno? . Quale sarà il filtro?
brasofilo,

1
Mi hai frainteso. Uso le 990 immagini nei post, non uso il dispositivo di scorrimento nella home. Alcuni di loro mi servono i pollici per il portafoglio, altri i pollici per i blog, ecc.
chifliiiii

Risposte:


12

Dai un'occhiata al plug-in Dynamic Image Resizer di Otto

Questo plugin cambia il modo in cui WordPress crea immagini per farle generare solo quando sono effettivamente utilizzate da qualche parte, al volo. Le immagini così create verranno salvate nelle normali directory di upload, per un successivo invio rapido da parte del server web. Il risultato è che lo spazio viene risparmiato (poiché le immagini vengono create solo quando necessario) e il caricamento delle immagini è molto più veloce (poiché non genera più le immagini durante il caricamento).


2
Si noti che il plug-in ha un problema con l'aggiunta di immagini ai vecchi post. Patch benvenute.
Otto,

Questo è esattamente quello che stavo cercando. Ci proverò. Quindi funziona solo su nuovi post?
chifliiiii,

1
Per coloro che si imbattono in questo post ora, ecco un plug-in simile che sembra essere attivamente sviluppato: wordpress.org/plugins/fly-dynamic-image-resizer
Tim Malone

7

Inseriscilo nel file delle funzioni del tema. Impedirà a Wordpress di creare qualsiasi cosa tranne le 3 dimensioni predefinite durante il caricamento.

Quando un'immagine viene quindi richiesta in una dimensione particolare, che non è stata ancora generata, verrà creata solo una volta.

        add_filter('image_downsize', 'ml_media_downsize', 10, 3);
        function ml_media_downsize($out, $id, $size) {
            // If image size exists let WP serve it like normally
            $imagedata = wp_get_attachment_metadata($id);
            if (is_array($imagedata) && isset($imagedata['sizes'][$size]))
                return false;

            // Check that the requested size exists, or abort
            global $_wp_additional_image_sizes;
            if (!isset($_wp_additional_image_sizes[$size]))
                return false;

            // Make the new thumb
            if (!$resized = image_make_intermediate_size(
                get_attached_file($id),
                $_wp_additional_image_sizes[$size]['width'],
                $_wp_additional_image_sizes[$size]['height'],
                $_wp_additional_image_sizes[$size]['crop']
            ))
                return false;

            // Save image meta, or WP can't see that the thumb exists now
            $imagedata['sizes'][$size] = $resized;
            wp_update_attachment_metadata($id, $imagedata);

            // Return the array for displaying the resized image
            $att_url = wp_get_attachment_url($id);
            return array(dirname($att_url) . '/' . $resized['file'], $resized['width'], $resized['height'], true);
        }


        add_filter('intermediate_image_sizes_advanced', 'ml_media_prevent_resize_on_upload');
        function ml_media_prevent_resize_on_upload($sizes) {
            // Removing these defaults might cause problems, so we don't
            return array(
                'thumbnail' => $sizes['thumbnail'],
                'medium' => $sizes['medium'],
                'large' => $sizes['large']
            );
        }

Questo filer dovrebbe essere standard in WordPress. Perché generare ogni dimensione per ogni immagine? Sto aggiungendo questo codice ai miei temi personalizzati. Grazie
Michaelkay,

2
Bello ma ora genererà ancora tutte le immagini se avessi bisogno di una sola dimensione personalizzata ..
Gijs

Succede quando uso oggetti immagine da campi personalizzati avanzati
Gijs

Non funziona SE add_image_size è stato precedentemente definito con le dimensioni dell'immagine appena cambiate
Benjamin Intal

@Michaelkay c'è una penalità di prestazione in questo approccio. Quando le immagini vengono caricate e quindi generate per ogni dimensione, significa che l'autore del caricamento è quello con pazienza. Questo codice fa sì che i tuoi visitatori debbano avere più pazienza e Google ha dimostrato che i siti che richiedono più di 2 secondi per caricare, fanno perdere il 50% delle persone. Inoltre, se il tuo sito ha centinaia di visite simultanee, questo eliminerà i tuoi server.
Tom Roggero

2

Sfortunatamente la risposta di @ Patrick rompe le funzioni di srcset introdotte in WP 4.4. Fortunatamente, dobbiamo solo aggiungere due funzioni aggiuntive!

Innanzitutto, è necessario reintrodurre temporaneamente tutte le dimensioni delle miniature registrate nei metadati dell'immagine in modo che possano essere considerati:

function bi_wp_calculate_image_srcset_meta($image_meta, $size_array, $image_src, $attachment_id){
    //all registered sizes
    global $_wp_additional_image_sizes;

    //some source file specs we'll use a lot
    $src_path = get_attached_file($attachment_id);
    $src_info = pathinfo($src_path);
    $src_root = trailingslashit($src_info['dirname']);
    $src_ext = $src_info['extension'];
    $src_mime = wp_check_filetype($src_path);
    $src_mime = $src_mime['type'];
    $src_base = wp_basename($src_path, ".$src_ext");

    //find what's missing
    foreach($_wp_additional_image_sizes AS $k=>$v)
    {
        if(!isset($image_meta['sizes'][$k]))
        {
            //first, let's find out how things would play out dimensionally
            $new_size = image_resize_dimensions($image_meta['width'], $image_meta['height'], $v['width'], $v['height'], $v['crop']);
            if(!$new_size)
                continue;
            $new_w = (int) $new_size[4];
            $new_h = (int) $new_size[5];

            //bad values
            if(!$new_h || !$new_w)
                continue;

            //generate a filename the same way WP_Image_Editor would
            $new_f = wp_basename("{$src_root}{$src_base}-{$new_w}x{$new_h}." . strtolower($src_ext));

            //finally, add it!
            $image_meta['sizes'][$k] = array(
                'file'      => $new_f,
                'width'     => $new_w,
                'height'    => $new_h,
                'mime-type' => $src_mime
            );
        }
    }

    return $image_meta;
}
add_filter('wp_calculate_image_srcset_meta', 'bi_wp_calculate_image_srcset_meta', 10, 4);

Quindi dobbiamo scorrere le partite e generare eventuali miniature mancanti:

function bi_wp_calculate_image_srcset($sources, $size_array, $image_src, $image_meta, $attachment_id){

    //get some source info
    $src_path = get_attached_file($attachment_id);
    $src_root = trailingslashit(pathinfo($src_path, PATHINFO_DIRNAME));

    //the actual image metadata (which might be altered here)
    $src_meta = wp_get_attachment_metadata($attachment_id);

    //an array of possible sizes to search through
    $sizes = $image_meta['sizes'];
    unset($sizes['thumbnail']);
    unset($sizes['medium']);
    unset($sizes['large']);

    $new = false;

    //loop through sources
    foreach($sources AS $k=>$v)
    {
        $name = wp_basename($v['url']);
        if(!file_exists("{$src_root}{$name}"))
        {
            //find the corresponding size
            foreach($sizes AS $k2=>$v2)
            {
                //we have a match!
                if($v2['file'] === $name)
                {
                    //make it
                    if(!$resized = image_make_intermediate_size(
                        $src_path,
                        $v2['width'],
                        $v2['height'],
                        $v2['crop']
                    )){
                        //remove from sources on failure
                        unset($sources[$k]);
                    }
                    else
                    {
                        //add the new thumb to the true meta
                        $new = true;
                        $src_meta['sizes'][$k2] = $resized;
                    }

                    //remove from the sizes array so we have
                    //less to search next time
                    unset($sizes[$k2]);
                    break;
                }//match
            }//each size
        }//each 404
    }//each source

    //if we generated something, update the attachment meta
    if($new)
        wp_update_attachment_metadata($attachment_id, $src_meta);

    return $sources;
}
add_filter('wp_calculate_image_srcset', 'bi_wp_calculate_image_srcset', 10, 5);

Solo un avvertimento per farti sapere che questo romperà il taglio duro! Mi ci sono volute ore per scoprire che questo era il colpevole. Sto lavorando a una soluzione ...
Constantin Groß,

1

In realtà, add_image_size()non genera l'anteprima, registra solo una dimensione dell'immagine come disponibile per WordPress.

In genere, le miniature vengono generate al primo caricamento dell'immagine. È un processo automatico, quindi non devi preoccuparti di generarli in seguito. Pensala in questo modo: se sono necessari 1-2 secondi per generare un'anteprima su un server lento e aspetti fino a quando non viene richiesto, imponi al richiedente di attendere altri 1-2 secondi per immagine per vedere il contenuto. È molto più semplice farlo in anticipo, ad esempio quando l'immagine viene caricata.

Allo stesso tempo, se devi assolutamente elaborare le miniature in un momento diverso, potresti dare un'occhiata al plug-in Rigenerate miniature di Viper . Utilizza un'azione su richiesta per rigenerare tutte le miniature delle immagini ... ma è possibile utilizzare un codice simile per generare miniature solo quando necessario.


Penso che non hai capito. Vuole controllare per quali immagini è necessaria una miniatura. Quindi alcune immagini non devono essere ridimensionate affatto.
Drunken Master

La maggior parte delle persone prova le pagine quando inseriscono le foto (mi sento abbastanza salvo dire tutto). Causeranno la generazione dei file necessari una volta e il gioco è fatto. Nel mio caso, ho registrato una dimensione dell'immagine dell'intestazione. Circa 1 su 20 immagini che carico sono in realtà per l'intestazione. Quindi 19 immagini su 20 nella mia biblioteca sono uno spreco di spazio.
JpaytonWPD,

1

C'è un modo per licenziare add_image_size solo quando necessario?

Non esattamente. Ma puoi filtrare l'elenco delle dimensioni registrate subito prima della generazione delle anteprime. La funzione wp_generate_attachment_metadata () (che chiama la funzione che genera le anteprime) ha un filtro chiamato "intermedio_immagine_avanzata", che consente di manipolare l'array di dimensioni appena prima della generazione dei file. È possibile utilizzare questo filtro ogni volta che si aggiunge un'immagine di un determinato "tipo", quindi rimuoverlo immediatamente dopo.

Immagino che la tua più grande sfida sarebbe quella di capire come differenziare le immagini che hanno bisogno di dimensioni extra e quelle che non lo fanno.


dovrei aggiungere un'opzione o una casella di controllo quando carico i media per scegliere quali pollici voglio generare, ad esempio. Sembra buono ma non ho idea di come farlo
Chifliiiii

1

Puoi usare il mio plug-in (non Ottos) "Dynamic Image Resize" 1) .

"Dynamic Image Resize" è un plug-in di WordPress (MU-) che offre uno shortcode e un tag modello per ridimensionare le immagini "in volo" senza la necessità di TimThumb, ma con le funzioni principali di WP.

Il plugin viene fornito con un tag modello e anche uno shortcode .

1) Ho appena scoperto il plugin Ottos. La collisione dei nomi non era prevista.



0

Il plug-in WP Performance Pack offre "una migliore gestione delle immagini", che si basa su Ottos Dynamic Image Resizer, ma include molti miglioramenti, ad esempio: innanzitutto è compatibile con l'ultima versione di WordPress (3.9.1), utilizza WP_Image_Editor, il salvataggio delle anteprime può essere disattivato (ma possono essere memorizzati nella cache e il supporto CDN è attivo), rigenerare l'integrazione delle miniature (per eliminare le miniature esistenti) e altro ancora.


-1

Puoi provare anche Aqua Resizer - https://github.com/syamilmj/Aqua-Resizer/

È solo un file.

Puoi usarlo in questo modo:

$img_src = aq_resize( $img_src, $width = null, $height = null, $crop = null, $single = true, $upscale = false );

$img_src = aq_resize( $img_src, 150, 150); // resized
$img_src = aq_resize( $img_src, 150, 150, true); // cropped
$img_src = aq_resize( $img_src, 150, 150, null, null, true); // image with 120x120 for example will be upscaled up to 150x150

-1

Ecco ancora un altro approccio: si aggancia alla gestione degli errori HTTP 404. Cioè, quando la miniatura non è disponibile, trova l'immagine originale e crea la miniatura. Nota che questo non risolve davvero il tuo problema, poiché non previene la generazione di miniature durante il caricamento.

Si noti inoltre che questo plug-in potrebbe essere utilizzato da utenti malintenzionati per creare un numero qualsiasi di miniature e quindi esaurire lo spazio su disco.

Nota: questo plug-in può essere facilmente installato utilizzando Pluginception .

<?php
/*
Plugin Name: Create thumbnails on demand
Plugin URI: 
Description: Create thumbnails instead of showing 404. Use in combination with "Broken Link Checker" to create all missing thumbnails.
Version: 0.1
Author: Jack Miller
Author URI: 
License: 
License URI: 
*/
add_filter('status_header', 'createThumbIf404');
function createThumbIf404($httpCodeString) //e.g. HTTP/1.1 200 OK 
{
    global $wp_query;
    error_reporting(E_ALL);
    ini_set('display_errors', 1);

    $httpCode = explode(" ", $httpCodeString);
    $httpCode = $httpCode[1];
    if ($httpCode == "404") {
        $requestUri = $_SERVER["REQUEST_URI"];
        $regex = '/^\/(wp-content\/uploads\/(?:[a-zA-Z0-9]*\/){2})(.*)-(.*)x(.*)\.jpg$/';
        preg_match($regex, $requestUri, $groups);
        if (sizeof($groups) === 5) {
            $baseDir  = $groups[1];
            $baseName = $groups[2];
            $sizeX    = $groups[3];
            $sizeY    = $groups[4];

            $oriImg = ctod_checkFile($baseDir, $baseName);
            if ($oriImg != null) {

                $image = wp_get_image_editor($baseDir . $oriImg);
                if (!is_wp_error($image)) {
                    $image->resize($sizeX, $sizeY, true);
                    $thumb = $baseDir . $baseName . '-' . $sizeX . 'x' . $sizeY . '.jpg';
                    $image->save($thumb);
                    ctod_sendImageAndExit($thumb);
                }
            }
        }
    }
}
//finds original image within $baseDir with $baseName.
//Returns file name including extension of original image or null.
function ctod_checkFile($baseDir, $baseName)
{
    $arr = array(
        ".jpg",
        ".JPG",
        ".jpeg",
        ".JPEG"
    );
    foreach ($arr as &$ext) {
        if (file_exists($baseDir . $baseName . $ext)) {
            return $baseName . $ext;
        }
    }
    return null;
}
//Read file at $path from disk and return it as HTTP JPG image request.
function ctod_sendImageAndExit($path)
{
    $fp = fopen($path, 'rb');
    header("Content-Type: image/jpeg");
    header("Content-Length: " . filesize($path));
    fpassthru($fp);
    exit();
}
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.