Comment puis-je faire recadrer add_image_size () par le haut?

20

J'ai une série de messages, tous avec des images en vedette, mais je dois pouvoir personnaliser le recadrage en haut à droite. Dans ce cas, j'ai besoin qu'ils soient rognés en haut à droite, mais il serait utile de savoir également comment positionner ce point moi-même.

À l'heure actuelle, la fonction add_image_size () prend son recadrage au centre de l'image. Pas toujours jolie !!

Doux Fuzz
la source

Réponses:

13

La génération d'image intermédiaire est extrêmement rigide. image_resize()le garde près du code et manque complètement de crochets.

La seule option pour cela est de se connecter wp_generate_attachment_metadataet d'écraser l'image générée par WP avec la vôtre (qui aura besoin d'un peu de image_resize()fourche).

J'ai besoin de cela pour travailler, donc je pourrais peut-être partager du code plus tard.

Ok, voici un exemple approximatif mais fonctionnel. Notez que la configuration du recadrage de cette manière nécessite une compréhension de imagecopyresampled().

add_filter('wp_generate_attachment_metadata', 'custom_crop');

function custom_crop($metadata) {

    $uploads = wp_upload_dir();
    $file = path_join( $uploads['basedir'], $metadata['file'] ); // original image file
    list( $year, $month ) = explode( '/', $metadata['file'] );
    $target = path_join( $uploads['basedir'], "{$year}/{$month}/".$metadata['sizes']['medium']['file'] ); // intermediate size file
    $image = imagecreatefromjpeg($file); // original image resource
    $image_target = wp_imagecreatetruecolor( 44, 44 ); // blank image to fill
    imagecopyresampled($image_target, $image, 0, 0, 25, 15, 44, 44, 170, 170); // crop original
    imagejpeg($image_target, $target, apply_filters( 'jpeg_quality', 90, 'image_resize' )); // write cropped to file

    return $metadata;
}
Rarst
la source
1
sonne un peu comme jouer avec le noyau !!
Mild Fuzz le
5
Non, jouer avec le noyau changerait la image_resizefonction. Rarst faisait valoir qu'il fallait se connecter au processus de redimensionnement, mais créer les tailles d'image vous-même manuellement.
TheDeadMedic
Puis-je demander si cela fonctionne toujours? Je viens d'implémenter le crochet dans mon fichier functions.php et j'ai mis en place les fonctions add_image_size (), mais les images recadrées sont toujours recadrées à partir du centre.
cr0z3r
@ cr0z3r Je ne connais aucune raison pour laquelle cela ne fonctionnera pas. Mais notez qu'il ne s'agit que d'un exemple de preuve de concept approximatif, plutôt que d'un code fiable significatif.
Rarst
Hm, curieusement, cela ne fonctionne pas sur mon thème - est-ce possible parce que je courais localement (j'en doute fortement)? Je vais l'avoir en ligne et je vous le montrerai bientôt.
cr0z3r
13

Le codex Wordpress a la réponse, c'est ci-dessous.

Définissez la taille de l'image en recadrant l'image et en définissant une position de recadrage:

add_image_size( 'custom-size', 220, 220, array( 'left', 'top' ) ); // Hard crop left top

Lors de la définition d'une position de recadrage, la première valeur du tableau est la position de recadrage sur l'axe x, la seconde est la position de recadrage sur l'axe y.

x_crop_position accepte «gauche» «centre» ou «droite». y_crop_position accepte «haut», «centre» ou «bas». Par défaut, ces valeurs sont définies par défaut sur «Centre» lors de l'utilisation du mode de recadrage dur.

Et le codex fait également référence à une page qui montre comment les positions des cultures agissent.

http://havecamerawilltravel.com/photographer/wordpress-thumbnail-crop

ewroman
la source
C'est génial, devrait être la réponse acceptée, je pense!
Dalton
7

J'ai développé une solution à ce problème qui ne nécessite pas de pirater le cœur: http://bradt.ca/archives/image-crop-position-in-wordpress/

J'ai également soumis un patch pour core: http://core.trac.wordpress.org/ticket/19393

Ajoutez-vous en tant que Cc sur le ticket pour montrer votre soutien pour qu'il soit ajouté au core.

Bradt
la source
2
La solution de @ Rarst ne modifie pas non plus les fichiers principaux. ;)
fuxia
1
@toscho Je suppose qu'il ne voulait pas dire que l'autre réponse modifie le code principal.
kaiser
3

Vous pouvez utiliser le plugin Thumbnail Crop Position pour sélectionner la position de recadrage de vos miniatures.

PoseLab
la source
0

Solution alternative ici: http://pixert.com/blog/cropping-post-featured-thumbnails-from-top-instead-of-center-in-wordpress-with-native-cropping-tool/

Ajoutez simplement ce code à functions.php, puis utilisez le plugin "Regenerate Thumbnails" ( https://wordpress.org/plugins/regenerate-thumbnails/ ):

function px_image_resize_dimensions( $payload, $orig_w, $orig_h, $dest_w, $dest_h, $crop ){

// Change this to a conditional that decides whether you want to override the defaults for this image or not.
if( false )
return $payload;

if ( $crop ) {
// crop the largest possible portion of the original image that we can size to $dest_w x $dest_h
$aspect_ratio = $orig_w / $orig_h;
$new_w = min($dest_w, $orig_w);
$new_h = min($dest_h, $orig_h);

if ( !$new_w ) {
$new_w = intval($new_h * $aspect_ratio);
}

if ( !$new_h ) {
$new_h = intval($new_w / $aspect_ratio);
}

$size_ratio = max($new_w / $orig_w, $new_h / $orig_h);

$crop_w = round($new_w / $size_ratio);
$crop_h = round($new_h / $size_ratio);

$s_x = 0; // [[ formerly ]] ==> floor( ($orig_w - $crop_w) / 2 );
$s_y = 0; // [[ formerly ]] ==> floor( ($orig_h - $crop_h) / 2 );
} else {
// don't crop, just resize using $dest_w x $dest_h as a maximum bounding box
$crop_w = $orig_w;
$crop_h = $orig_h;

$s_x = 0;
$s_y = 0;

list( $new_w, $new_h ) = wp_constrain_dimensions( $orig_w, $orig_h, $dest_w, $dest_h );
}

// if the resulting image would be the same size or larger we don't want to resize it
if ( $new_w >= $orig_w && $new_h >= $orig_h )
return false;

// the return array matches the parameters to imagecopyresampled()
// int dst_x, int dst_y, int src_x, int src_y, int dst_w, int dst_h, int src_w, int src_h
return array( 0, 0, (int) $s_x, (int) $s_y, (int) $new_w, (int) $new_h, (int) $crop_w, (int) $crop_h );

}
add_filter( 'image_resize_dimensions', 'px_image_resize_dimensions', 10, 6 );
Niente0
la source
Salut Niente0, bienvenue au WPSE et merci pour ta réponse. Pourriez-vous modifier votre message pour expliquer ce que fait votre code? Les publications sur les sites StackExchange doivent expliquer leur solution et inclure uniquement les liens hors site en tant que références, pas en tant que solutions entières. Merci encore!
Tim Malone