Дублированные эскизы изображений внутри спрайта php-изображения

Я работаю над темами тестирования linux, xampp и wordpress с style.css и index.php.

Я создал скрипт php используя GD библиотека, которая создает спрайт изображения. Он может условно создавать спрайт из заданной папки (glob) или из URL (массива). Он также масштабирует все эскизы на лету, чтобы соответствовать заданному ограничивающему прямоугольнику (не моя функция).

Моя проблема в том, что все миниатюры дублируются внутри следующих миниатюр. Как: Первое изображение дублируется в 2, 2 в 3, 3 в 4 (…). Однако правильное изображение всегда поверх дублированного изображения.

Я думаю, что у моей петли или слияния миниатюры есть проблемы, но я не уверен.

Вот мой код (по умолчанию создает спрайт из массива):

<?php

//////// PART 1 - DEFINE GLOBAL VARIABLES ////////

//// SPRITE IMAGES SOURCE ////
// 0 = Create sprite from memory - array()
// 1 = Create sprite from folder - glob()
$sprite_images_source = 0;

//// Use array as sprite images source ////
if($sprite_images_source == 0){
$images=array(
//// Example .PNGs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/444/f2f2f2.png&text=128x72.png',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/444/f2f2f2.png&text=1280x720.png',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/444/f2f2f2.png&text=72x128.png',
// Orientation: Vertical, bigger than bounding box
'https://dummyimage.com/720x1280/444/f2f2f2.png&text=720x1280.png',
// Square, smaller than bounding box
'https://dummyimage.com/200x200/444/f2f2f2.png&text=400x400.png',

//// Example .JPEGs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/666/f2f2f2.jpg&text=128x72.jpg',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/666/f2f2f2.jpg&text=1280x720.jpg',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/666/f2f2f2.jpg&text=72x128.jpg',
// Orientation: Vertical, bigger than bounding box
'https://dummyimage.com/720x1280/666/f2f2f2.jpg&text=720x1280.jpg',
// Square
'https://dummyimage.com/200x200/666/f2f2f2.jpg&text=200x200.jpg',

//// Example .GIFs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/888/f2f2f2.gif&text=128x72.gif',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/888/f2f2f2.gif&text=1280x720.gif',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/888/f2f2f2.gif&text=72x128.gif',
// Try to have 1/3/5/7 images to see empty space on sprite,
// and test colorize sprite background method with this

);

//// Use folder as sprite images source ////
} else if($sprite_images_source == 1){
// $images = glob('sprite/images/*');
}//// SINGLE THUMBNAIL = BOUNDING BOX DIMENSIONS ////
$thumbnail_width = 300;
$thumbnail_height = 300;
$thumbnail = imagecreatetruecolor($thumbnail_width, $thumbnail_height);//// SPRITE DIMENSIONS ////
$sprite_columns = 5;
$sprite_rows = ceil(count($images) / $sprite_columns);
$sprite_width = $thumbnail_width * $sprite_columns;
$sprite_height = $thumbnail_height * $sprite_rows;
$sprite = imagecreatetruecolor($sprite_width, $sprite_height);//// SPRITE BACKGROUND COLOR ////
$sprite_bg = imagecolortransparent($sprite, imagecolorallocatealpha($sprite, 0,0,0,0));
imagefill($sprite,0,0,$sprite_bg);//////// PART 2 - GENERATE SPRITE ////////

//// Assign each source from array to single image
foreach ($images as $i => $image) {
$images[$i] = array(
'src' => $image,
'title' => 'Product ' . ($i + 1),
'price' => '$' . ($i * 100)
);
}//// SINGLE THUMBNAIL MANIPULATION ////
// Start Generate Thumbnail from first file in array/folder
$i = 0;

for ($y = 0; $y < $sprite_height; $y += $thumbnail_height) {
for ($x = 0; $x < $sprite_width; $x += $thumbnail_width) {
// What is this for ???
if ($i >= count($images)) {
break 2;
}

// Assosiate correct image for thumbnail from array
$image = $images[$i];
$src = imagecreatefromstring(file_get_contents($image['src']));

// Scale Image to Bounding Box
scale_image($src, $thumbnail, 'fit');//// PRINT IMAGE INTO SINGLE THUMBNAIL ////
imagecopy($sprite, $thumbnail, $x, $y, 0, 0, $thumbnail_width, $thumbnail_height);
imagedestroy($src);
$i++;
}
// END | for ($y = 0; $y < $sprite_height; $y += $thumbnail_height)
}
// END | for ($y = 0; $y < $sprite_height; $y += $thumbnail_height)//////// PART 3 - OUTPUT SPRITE ////////

// Output Sprite to Browser as PNG
header('Content-Type: image/png');
imagepng($sprite);

// Clean up, and free memory
imagedestroy($thumbnail);
imagedestroy($sprite);// FUNCTION - SCALE IMAGE
function scale_image($src_image, $dst_image, $op = 'fit') {
$src_width = imagesx($src_image);
$src_height = imagesy($src_image);

$dst_width = imagesx($dst_image);
$dst_height = imagesy($dst_image);

// Try to match destination image by width
$new_width = $dst_width;
$new_height = round($new_width*($src_height/$src_width));
$new_x = 0;
$new_y = round(($dst_height-$new_height)/2);

// FILL and FIT mode are mutually exclusive
if ($op =='fill')
$next = $new_height < $dst_height;
else
$next = $new_height > $dst_height;

// If match by width failed and destination image does not fit, try by height
if ($next) {
$new_height = $dst_height;
$new_width = round($new_height*($src_width/$src_height));
$new_x = round(($dst_width - $new_width)/2);
$new_y = 0;
}

// Copy image on right place
imagecopyresampled($dst_image, $src_image , $new_x, $new_y, 0, 0, $new_width, $new_height, $src_width, $src_height);
}

1

Решение

Переместить эту строку кода

$thumbnail = imagecreatetruecolor($thumbnail_width, $thumbnail_height);

После этих строк и

    for ($y = 0; $y < $sprite_height; $y += $thumbnail_height) {
for ($x = 0; $x < $sprite_width; $x += $thumbnail_width) {
// What is this for ???
if ($i >= count($images)) {
break 2;
}
################## MOVE THAT LINE HERE ##################

и не забудьте использовать

imagedestroy($thumbnail);

до окончания цикла.

Надеюсь, это поможет удалить перекрывающиеся изображения.

ОБНОВИТЬ
Ваш код работает, и проблема заключалась в повторении дескриптора эскиза. Вот результирующий снимок по сравнению с моим предыдущим ответом.

Вот результат успеха по сравнению с моим предыдущим ответом ... [1]

0

Другие решения

Габриель, мой английский беднее тебя. Позвольте мне помочь вам, чтобы помочь себе …

На самом деле проблема с вашим $thumbnail обработка, которая хранится внутри scale_image функция в $dst_imageВот почему это повторяется …

Я пробовал писать (imagepng($thumbnail,'images/image_xyzzz_i.png');) $thumbnail и уничтожить это. Были созданы перекрывающиеся изображения. Пока я пытался уничтожить $dst_image внутри scale_image функция, она уничтожена $thumbnail тоже. Избавьтесь от этого отношения.

ОБНОВИТЬ….

Вы можете ясно видеть, что на спрайт влияет только $thumbnail ,

Результат для миниатюры на разных этапах

ОБНОВЛЕНИЕ — 2

Вот ваш модифицированный код … Просто две копии и вставки …

<?php

//////// PART 1 - DEFINE GLOBAL VARIABLES ////////

//// SPRITE IMAGES SOURCE ////
// 0 = Create sprite from memory - array()
// 1 = Create sprite from folder - glob()
$sprite_images_source = 0;

//// Use array as sprite images source ////
if($sprite_images_source == 0){
$images=array(
//// Example .PNGs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/444/f2f2f2.png&text=128x72.png',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/444/f2f2f2.png&text=1280x720.png',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/444/f2f2f2.png&text=72x128.png',
// Orientation: Vertical, bigger than bounding box
'https://dummyimage.com/720x1280/444/f2f2f2.png&text=720x1280.png',
// Square, smaller than bounding box
'https://dummyimage.com/200x200/444/f2f2f2.png&text=400x400.png',

//// Example .JPEGs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/666/f2f2f2.jpg&text=128x72.jpg',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/666/f2f2f2.jpg&text=1280x720.jpg',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/666/f2f2f2.jpg&text=72x128.jpg',
// Orientation: Vertical, bigger than bounding box
'https://dummyimage.com/720x1280/666/f2f2f2.jpg&text=720x1280.jpg',
// Square
'https://dummyimage.com/200x200/666/f2f2f2.jpg&text=200x200.jpg',

//// Example .GIFs ////
// Orientation: Horizontal, smaller than bounding box
'https://dummyimage.com/128x72/888/f2f2f2.gif&text=128x72.gif',
// Orientation: Horizontal, bigger than bounding box
'https://dummyimage.com/1280x720/888/f2f2f2.gif&text=1280x720.gif',
// Orientation: Vertical, smaller than bounding box
'https://dummyimage.com/72x128/888/f2f2f2.gif&text=72x128.gif',
// Try to have 1/3/5/7 images to see empty space on sprite,
// and test colorize sprite background method with this

);

//// Use folder as sprite images source ////
} else if($sprite_images_source == 1){
// $images = glob('sprite/images/*');
}//// SINGLE THUMBNAIL = BOUNDING BOX DIMENSIONS ////
$thumbnail_width = 300;
$thumbnail_height = 300;
################# CUT LINE 1 FROM HERE ########################//// SPRITE DIMENSIONS ////
$sprite_columns = 5;
$sprite_rows = ceil(count($images) / $sprite_columns);
$sprite_width = $thumbnail_width * $sprite_columns;
$sprite_height = $thumbnail_height * $sprite_rows;
$sprite = imagecreatetruecolor($sprite_width, $sprite_height);//// SPRITE BACKGROUND COLOR ////
$sprite_bg = imagecolortransparent($sprite, imagecolorallocatealpha($sprite, 0,0,0,0));
imagefill($sprite,0,0,$sprite_bg);//////// PART 2 - GENERATE SPRITE ////////

//// Assign each source from array to single image
foreach ($images as $i => $image) {
$images[$i] = array(
'src' => $image,
'title' => 'Product ' . ($i + 1),
'price' => '$' . ($i * 100)
);
}//// SINGLE THUMBNAIL MANIPULATION ////
// Start Generate Thumbnail from first file in array/folder
$i = 0;

for ($y = 0; $y < $sprite_height; $y += $thumbnail_height) {
for ($x = 0; $x < $sprite_width; $x += $thumbnail_width) {
// What is this for ???
if ($i >= count($images)) {
break 2;
}############################# PASTED LINE 1 HERE ######################
$thumbnail = imagecreatetruecolor($thumbnail_width, $thumbnail_height);
#######################################################################

// Assosiate correct image for thumbnail from array
$image = $images[$i];
$src = imagecreatefromstring(file_get_contents($image['src']));

// Scale Image to Bounding Box
scale_image($src, $thumbnail, 'fit');//// PRINT IMAGE INTO SINGLE THUMBNAIL ////
imagecopy($sprite, $thumbnail, $x, $y, 0, 0, $thumbnail_width, $thumbnail_height);
imagedestroy($src);
$i++;

######################## PASTED LINE 2 HERE ###########################
imagedestroy($thumbnail);
#######################################################################

}
// END | for ($y = 0; $y < $sprite_height; $y += $thumbnail_height)
}
// END | for ($y = 0; $y < $sprite_height; $y += $thumbnail_height)//////// PART 3 - OUTPUT SPRITE ////////

// Output Sprite to Browser as PNG
header('Content-Type: image/png');
imagepng($sprite);

// Clean up, and free memory
######################## CUT LINE 2 HERE ###########################
imagedestroy($sprite);// FUNCTION - SCALE IMAGE
function scale_image($src_image, $dst_image, $op = 'fit') {
$src_width = imagesx($src_image);
$src_height = imagesy($src_image);

$dst_width = imagesx($dst_image);
$dst_height = imagesy($dst_image);

// Try to match destination image by width
$new_width = $dst_width;
$new_height = round($new_width*($src_height/$src_width));
$new_x = 0;
$new_y = round(($dst_height-$new_height)/2);

// FILL and FIT mode are mutually exclusive
if ($op =='fill')
$next = $new_height < $dst_height;
else
$next = $new_height > $dst_height;

// If match by width failed and destination image does not fit, try by height
if ($next) {
$new_height = $dst_height;
$new_width = round($new_height*($src_width/$src_height));
$new_x = round(($dst_width - $new_width)/2);
$new_y = 0;
}

// Copy image on right place
imagecopyresampled($dst_image, $src_image , $new_x, $new_y, 0, 0, $new_width, $new_height, $src_width, $src_height);
}
0