Автоматическое создание thumbnails (тумбы, превьюшки) на PHP
Иногда бывает необходимо закачать картинку единожды, а потом выложить на сайт в любое время, в любом формате, размере и типе файла.
Возможный url для вставки картинки может быть таким: http://www.example.com/img.php?f(filename)+w(300).
Используя этот url, мы можем вставить картинку с именем filename, размером 300px по ширине и соответствующей высоте.
Определимся с возможностями скрипта:
1. Изменение размеров изображения по ширине или высоте с сохранением пропорций.
2. Устанавка размера нового изображения как в пикселах, так и в процентах от исходной картинки.
3. Изменение размеров изображения в случае превышения определенного значения.
4. Возврат изображения в .jpg или .png формате.
Необходимое.
Для написания этого скрипта нам нужен собственно PHP и графическая библиотека GD.
Синтаксис для работы со скриптом.
Для вызова скрипта будем использовать определенный синтаксис. Все аргументы будем разделять только знаками минуса(-) или плюса(+): http://www.example.com/img.php?f(filename)+w(300).
f(filename) - имя запрашиваемого изображения. Файл с изображением должен быть сохранен на сервере БЕЗ расширения, длина имени файла - 13 символов, например fjghtykbndohj.
w(123) или w(10%) - необходимая ширина изображения на выходе. Задается в пикселах или процентах.
h(123) или h(10%) - то же самое для высоты результирующего изображения.
x(123) или y(123) - значение ширины или высоты, превышать которое не допустимо.
t(png|jpg) - установка типа файла, в котором надо вывести результирующее изображение. Если значение не задано, тип устанавливается аналогичным исходному файлу.
q(100) - только для файлов jpg. Устанавливает качество результирующего изображения. Принимает значения от 0 до 100.
Теперь давайте рассмотрим код самого скрипта.
Проверка аргументов.
Перво-наперво, проверим переданные аргументы из строки запроса простеньким регулярным выражением, возвращающим все переданные аргументы. Полученные значения проверяем на неправильные значения, и если все правильно, сохраняем в ассоциативный массив для дальнейшего использования. А так же проверяем, существует ли запрашиваемый файл.
<?
// папка с
изображениями
$base_img_dir = "./img/";
// поиск
аргументов
preg_match_all("/+*(([a-z])(([^)]+)))+*/",
$QUERY_STRING,
$matches, PREG_SET_ORDER);
// пустой массив и выражения для
проверки аргументов
$tags = array();
$check = array( "f" =>
"[0-9a-zA-Z]{13}",
"w" => "[0-9]+%?",
"h" => "[0-9]+%?",
"x"
=> "[0-9]+",
"y" => "[0-9]+",
"t" => "jpg|png",
"q" =>
"1?[0-9]{1,2}" );
// проверка значений аргументов и сохранение в
массив
for ($i=0; $i<count($matches); $i++) {
if
(isset($check[$matches[$i][2]])) {
if
(preg_match('/^('.$check[$matches[$i][2]].')$/',
$matches[$i][3]))
{
$tags[$matches[$i][2]] = $matches[$i][3];
}
}
}
function
notfound() {
header("HTTP/1.0 404 Not Found");
exit;
}
// проверим,
что имя файла передано
if (!isset($tags["f"])) {
notfound();
}
//
проверим, что файл существует
if (!file_exists($base_img_dir.$tags["f"]))
{
notfound();
}
?>
Загрузка изображения.
Следующим шагом осуществим загрузку картинки.
<?
// получаем информацию об
изображении
$imginfo = getimagesize($base_img_dir.$tags["f"]);
//
загружаем его
switch ($imginfo[2]) {
case 2: // jpg
$img_in =
imagecreatefromjpeg($base_img_dir.$tags["f"]) or notfound();
if
(!isset($tags["t"])) {
$tags["t"] = "jpg";
}
break;
case 3: //
png
$img_in = imagecreatefrompng($base_img_dir.$tags["f"]) or
notfound();
if (!isset($tags["t"])) {
$tags["t"] =
"png";
}
break;
default:
notfound();
}
?>
Изменение размеров изображения.
<?
// проверяем максимальные ширину и
высоту
if (isset($tags["x"])) {
if ($tags["x"] < imagesx($img_in))
{
$tags["w"] = $tags["x"];
}
}
if (isset($tags["y"])) {
if
($tags["y"] < imagesy($img_in)) {
$tags["h"] = $tags["y"];
}
}
//
проверяем необходимость изменения размера
if (isset($tags["h"]) or
isset($tags["w"])) {
// convert relative to absolute
if
(isset($tags["w"])) {
if (strstr($tags["w"], "%")) {
$tags["w"] =
(intval(substr($tags["w"], 0, -1)) / 100) *
$imginfo[0];
}
}
if
(isset($tags["h"])) {
if (strstr($tags["h"], "%")) {
$tags["h"] =
(intval(substr($tags["h"], 0, -1)) / 100) *
$imginfo[1];
}
}
//
изменениe размера
if (isset($tags["w"]) and isset($tags["h"])) {
$out_w =
$tags["w"];
$out_h = $tags["h"];
} elseif (isset($tags["w"]) and
!isset($tags["h"])) {
$out_w = $tags["w"];
$out_h = $imginfo[1] *
($tags["w"] / $imginfo[0]);
} elseif (!isset($tags["w"]) and
isset($tags["h"])) {
$out_w = $imginfo[0] * ($tags["h"] /
$imginfo[1]);
$out_h = $tags["h"];
} else {
$out_w =
$tags["w"];
$out_h = $tags["h"];
}
// вывод нового изображения в
$img_out
$img_out = imagecreate($out_w,
$out_h);
imagecopyresized($img_out, $img_in, 0, 0, 0, 0,
imagesx($img_out),
imagesy($img_out), imagesx($img_in),
imagesy($img_in));
} else {
// изменять размеры не надо
$img_out =
$img_in;
}
?>
Вывод изображения.
<?
// проверяем, надо ли установить
качество в случае если на выходе jpg
if (!isset($tags["q"])) {
$tags["q"]
= 75;
}
// вывод изображения
switch ($tags["t"]) {
case
"jpg":
header("Content-type: image/jpeg");
imagejpeg($img_out, "",
$tags["q"]);
exit;
case "png":
header("Content-type:
image/png");
imagepng($img_out);
exit;
default:
notfound();
}
?>
Рекомендуем почитать